package com.watchthelan.repository;

import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.List;

import javax.print.attribute.standard.Severity;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.jdbc.core.namedparam.MapSqlParameterSource;
import org.springframework.jdbc.core.simple.ParameterizedRowMapper;
import org.springframework.jdbc.core.simple.SimpleJdbcDaoSupport;

import com.watchthelan.domain.Server;

public class JdbcServerDao extends SimpleJdbcDaoSupport implements ServerDao {

	/** Logger for this class and subclasses */
	protected final Log logger = LogFactory.getLog(getClass());

	public void addServer(Server server) {
		logger.info("adding server: " + server);
		int id = getSimpleJdbcTemplate().queryForInt("select max(id) from servers", new HashMap<String, String>()) + 1;
		logger.info("next id: " + id);
		int count = getSimpleJdbcTemplate().update(
				"insert into servers (id, name, hostname, port, description, status) values(:id, :name, :hostname, :port, :description, :status)",
				new MapSqlParameterSource().addValue("id", id)
				.addValue("name", server.getName())
				.addValue("hostname", server.getHostname())
				.addValue("port", server.getPort())
				.addValue("description", server.getDescription())
				.addValue("status", server.getStatus()));
		logger.info("Rows affected: " + count);
	}

	public List<Server> getServers() {
		logger.info("get servers");
		List<Server> servers = getSimpleJdbcTemplate().query("select id, name, hostname, description, port, status from servers", new ServerMapper());		
		return servers;
	}


	private static class ServerMapper implements ParameterizedRowMapper<Server> {

		public Server mapRow(ResultSet rs, int arg1) throws SQLException {
			Server server = new Server();
			server.setId(rs.getLong("id"));
			server.setName(rs.getString("name"));
			server.setHostname(rs.getString("hostname"));
			server.setDescription(rs.getString("description"));
			server.setPort(rs.getInt("port"));
			server.setStatus(rs.getInt("status"));
			server.setHostname(rs.getString("hostname"));
			return server;
		}

	}

	public void deleteServerById(Long id) {
		logger.info("deleting server with id " + id);
		int count = getSimpleJdbcTemplate().update(
				"delete from servers where id=:id",
				new MapSqlParameterSource().addValue("id", id));
		logger.info("Rows affected: " + count);
	}

	public Server getServerById(Long id) {
		logger.info("get server by id");
		if (id == null) {
			logger.info("server id is null");
			return null;
		}
		Server server = null;
		List<Server> serverList = getSimpleJdbcTemplate().query("select * from servers where id=?", 
				new ServerRowMapper(), id);
		if (serverList != null && serverList.size() > 0) {
			server = serverList.get(0);
			server.setId(id);
			logger.info("got server: " + server);
		}
		return server;
	}

	public void updateServer(Server server) {
		logger.info("updating server: " + server);
		int count = getSimpleJdbcTemplate().update(
				"update servers set id=:id, name=:name, hostname=:hostname, port=:port, description=:description, status=:status where id=:id",
				new MapSqlParameterSource().addValue("id", server.getId())
				.addValue("name", server.getName())
				.addValue("hostname", server.getHostname())
				.addValue("port", server.getPort())
				.addValue("description", server.getDescription())
				.addValue("status", server.getStatus()));
		logger.info("Rows affected: " + count);		
	}

	@Override
	public List<Server> getServersOwnedBy(Long id) {
		logger.info("Get servers owned by Administrator with id " + id);
		List<Server> servers = getSimpleJdbcTemplate().query("select id, name, hostname, description, port, status " +
				"from servers " +
				"where owner=?", 
				new ServerRowMapper(), id);		
		return servers;
	}
	
	private static class ServerRowMapper implements ParameterizedRowMapper<Server> {
		public Server mapRow(ResultSet rs, int rowNum)
		throws SQLException {
			Server server = new Server();
			server.setName(rs.getString("name"));
			server.setHostname(rs.getString("hostname"));
			server.setPort(rs.getInt("port"));
			server.setStatus(rs.getInt("status"));
			server.setDescription(rs.getString("description"));

			return server;
		}
	}
}
